
public class ALU {
	int Opcode;
	int Operand1;
	int Operand2;
	int ALU_OUT;
	
	int ALU_prev;
	int wb_perv;
	int alu_Op1_Sel;
	int alu_Op2_Sel;
	
	
	void init(){
		Opcode=0;
		Operand1=0;
		Operand2=0;
	}
	
	void set_Opcode(int regwe){
		Opcode=regwe;
	}
	void set_Operand1(int regwe){
		Operand1=regwe;
	}
	void set_Operand2(int regwe){
		Operand2=regwe;
	}
	void go(){
		if(alu_Op1_Sel==1){
			Operand1=ALU_prev;
		}
		if(alu_Op1_Sel==2){
			Operand1=wb_perv;
		}
		if(alu_Op2_Sel==1){
			Operand2=ALU_prev;
		}
		if(alu_Op2_Sel==2){
			Operand2=wb_perv;
		}
		switch(Opcode){
			case 0x4:	//SLL
				ALU_OUT=Operand1 << Operand2;
				break;
			case 0x6:	//SRL
				ALU_OUT=Operand1 >>> Operand2;
				break;
			case 0x7:	//SRA
				ALU_OUT=Operand1 >> Operand2;
				break;				
			case 0x20:	//ADD
				ALU_OUT=Operand1+Operand2;
				break;
			case 0x21:	//ADDU
				ALU_OUT=Operand1+Operand2;
				break;
			case 0x22:	//SUB
				ALU_OUT=Operand1-Operand2;
				break;
			case 0x23:	//SUBU
				ALU_OUT=Operand1-Operand2;
				break;
			case 0x24:	//AND
				ALU_OUT=Operand1 & Operand2;
				break;
			case 0x25:	//OR
				ALU_OUT=Operand1 | Operand2;
				break;
			case 0x26:	//XOR
				ALU_OUT=Operand1 ^ Operand2;
				break;
			case 0x28:	//SEQ
				if(Operand1==Operand2){
					ALU_OUT=1;
				}else{
					ALU_OUT=0;
				}
				break;
			case 0x29:	//SNE
				if(Operand1!=Operand2){
					ALU_OUT=1;
				}else{
					ALU_OUT=0;
				}
				break;
			case 0x2a:	//SLT
				if(Operand1<Operand2){
					ALU_OUT=1;
				}else{
					ALU_OUT=0;
				}
				break;
			case 0x2b:	//SGT
				if(Operand1>Operand2){
					ALU_OUT=1;
				}else{
					ALU_OUT=0;
				}
				break;
			case 0x2c:	//SLE
				if(Operand1<=Operand2){
					ALU_OUT=1;
				}else{
					ALU_OUT=0;
				}
				break;
			case 0xe:	//MULT
				ALU_OUT=Operand1*Operand2;
				break;
			case 0xf:	//DIV
				ALU_OUT=Operand1/Operand2;
				break;
			case 0x16:	//MULTU
				ALU_OUT=Operand1*Operand2;
				break;
			case 0x17:	//DIVU
				ALU_OUT=Operand1/Operand2;
				break;
			case 0:
				ALU_OUT=0;
				break;
		}
	}
	int get_ALU_Out(){
		return ALU_OUT;
	}	
}
